#include "mylogin.h"
#include "ui_mylogin.h"

QHostAddress DeviceHost;

MyLogin::MyLogin(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::MyLogin)
{
    ui->setupUi(this);
    udp_socket=new QUdpSocket(this);
    tcp_socket=new QTcpSocket(this);
    file_socket=new QTcpSocket(this);

    //心跳包发送定时器初始化
    heart_pack_tm= new QTimer(this);
    heart_pack_tm->setInterval(HEART_TIME);
    heart_pack_tm->setSingleShot(false);
    //超时检测定时器初始化
    time_out_tm=new QTimer(this);
    time_out_tm->setInterval(TIME_OUT);
    time_out_tm->setSingleShot(true);

    connect(ui->search_pushButton,SIGNAL(clicked()),this,SLOT(searchButtonClickedSlot()));
    connect(ui->connect_btn, SIGNAL(clicked()), this, SLOT(linkButtonClickedSlot()));
    connect(ui->listWidget,SIGNAL(itemClicked(QListWidgetItem*)),this,SLOT(listItemSlot(QListWidgetItem*)));
    //udp连接信号槽
    connect(udp_socket, SIGNAL(readyRead()),this,SLOT(searchDeviceSlot()));
    //定时器信号槽
    connect(heart_pack_tm,SIGNAL(timeout()),this,SLOT(heartPackSendSlot()));
    connect(time_out_tm,SIGNAL(timeout()),this,SLOT(TimeOutSlot()));
    connect(ui->comboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(onIndexChanged(int)));
}

MyLogin::~MyLogin()
{
    delete ui;
}

void MyLogin::searchButtonClickedSlot()
{
     qDebug()<<"开始搜索";
    QHostAddress broadcast_ip ("192.168.31.255");
    udp_socket->writeDatagram("qulaobanNB", broadcast_ip, 8848);  // 发送广播消息
}

void MyLogin::searchDeviceSlot()
{
    while(udp_socket->hasPendingDatagrams())
    {
        qDebug()<<"1";
        QByteArray data;
        data.resize(udp_socket->pendingDatagramSize());
        QHostAddress host;
        quint16 port;
        udp_socket->readDatagram(data.data(), data.size(), &host, &port);
        QString text=QString(data);
        qDebug()<<host.toString()<<"    "<<port<<"    "<<text;
        if(text.startsWith("veryyes"))
        {
            qDebug()<<"yes";
            struct dev_addr dev;
            dev.dev_host=host;
            dev.dev_port=8838;
            dev.dev_name=text.mid(8);
            devList<<dev;
            ui->listWidget->addItem(new QListWidgetItem(dev.dev_name));
        }
    }
}

void MyLogin::listItemSlot(QListWidgetItem *item)
{
    qDebug()<<item->text();
    ui->label_dev->setText(item->text());
}

void MyLogin::linkButtonClickedSlot()
{
    qDebug()<<"开始";
    if(tcp_socket->isOpen())
    {
        tcp_socket->close();
    }
    bool dev_flag=false;
    QHostAddress host;
    quint16 port;
    foreach(struct dev_addr dev,devList)
    {
        if(!ui->label_dev->text().compare(dev.dev_name))
        {
            host=dev.dev_host;
            port=dev.dev_port;
            dev_flag=true;
        }
        qDebug()<<dev.dev_name;
    }
    if(!dev_flag)
    {
        QMessageBox::critical(this,"提示", "没有此设备!");
        return;
    }
    qDebug()<<host.toString()<<" "<<port;
    DeviceHost=host;
    tcp_socket->connectToHost(host,port);
    connect(tcp_socket,SIGNAL(readyRead()),this,SLOT(readyReadSlot()));
    connect(tcp_socket,SIGNAL(connected()), this,SLOT(connectedSlot()));
    connect(tcp_socket,SIGNAL(disconnected()), this,SLOT(disConnectedSlot()));
}

void MyLogin::readyReadSlot()
{
    QByteArray buffer=tcp_socket->readAll();
    QString json_text=QString(buffer);
    qDebug()<<"json: "<<json_text;
    QJsonParseError jsonError;
    // 将json解析为UTF-8编码的json文档，并从中创建一个QJsonDocument。
    // 如果解析成功，返回QJsonDocument对象，否则返回null
    QJsonDocument doc = QJsonDocument::fromJson(json_text.toUtf8(), &jsonError);
    // 判断是否解析失败
    if (jsonError.error != QJsonParseError::NoError && !doc.isNull()) {
        qDebug() << "Json格式错误！" << jsonError.error;
        return;
    }
    QJsonObject rootObj = doc.object();
    QJsonValue typeValue = rootObj.value("type");
    if(typeValue==1)
    {
        qDebug() << "type = " << typeValue;
        QJsonValue upconfigValue = rootObj.value("up_config");
        qDebug()<<upconfigValue.toBool();
        if(upconfigValue.toBool())
        {
            //qDebug()<<"no exit";
            //点表路径
            QString path=":/new/prefix1/node.json";

            //发送type2 开始包，开始进行下发点表
            QJsonObject root2;
            root2.insert("type",2);
            QJsonObject data_root;
            data_root.insert("flag","start");
            data_root.insert("file_name","node.json");
            data_root.insert("file_len",QFileInfo(path).size());
            root2.insert("data",data_root);

            QString text=QString(QJsonDocument(root2).toJson());
            char data[N]={};
            strcpy(data,text.toLatin1().data());
            tcp_socket->write(data,N);
            qDebug()<<"send:"<<data;

            //连接copy线程服务器
            QHostAddress ip=tcp_socket->peerAddress();
            int port=8878;
            file_socket->connectToHost(ip,port);
            connect(file_socket,SIGNAL(connected()),this,SLOT(copyConnectedSlot()));
            connect(file_socket,SIGNAL(disconnected()),this,SLOT(copyDisConnectedSlot()));

            //开始copy点表
            QFile readFile(path);
            // 打开文件流
            readFile.open(QIODevice::ReadOnly); // 只读模式
            while(!readFile.atEnd())    // 判断是否读到文件尾部
            {
                QByteArray array = readFile.read(1024);    // 每次读取1kb
                qint64 writeRet = file_socket->write(array);// 写出数据，返回值为本次写出的大小
                if(writeRet == -1)  // 如果写出函数的返回值为-1，表示写出失败
                {
                    qDebug()<<"点表下发失败";
                    break;
                }
            }
            // 关闭数据流
            readFile.close();
            //断开连接
            file_socket->close();
        }
        else
        {
            //更新点表配置
        }
    }
    if(typeValue==2)
    {
        QJsonObject dataitem = rootObj.value("data").toObject();
        QJsonValue flagvalue = dataitem.value("flag");
        qDebug()<<flagvalue.toString();
        if(flagvalue.toString().compare("stop")==0)
        {
            qDebug()<<"下发点表完成";
        }
    }
    if(typeValue==3)
    {
        qDebug() << "设备正常连接";
        time_out_tm->stop();
    }
}

void MyLogin::connectedSlot()
{
    ui->connect_btn->setText("已连接");
    ui->connect_btn->setEnabled(false);
    qDebug()<<"主线程已连接";

    heart_pack_tm->start();
    //下发type1 包
    QJsonObject startPackRoot;
    startPackRoot.insert("type", 1);
    QString text=QString(QJsonDocument(startPackRoot).toJson());
    char data[N]={};
    strcpy(data,text.toLatin1().data());
    tcp_socket->write(data,N);
    qDebug()<<data;
}

void MyLogin::disConnectedSlot()
{
    ui->connect_btn->setText("连接");
    ui->connect_btn->setEnabled(true);
    qDebug()<<"主线程断开连接" ;
}

void MyLogin::copyConnectedSlot()
{
    qDebug()<<"copy 线程连接成功" ;
}

void MyLogin::copyDisConnectedSlot()
{
    //发送type2 停止包
    QJsonObject root2;
    QJsonObject data_root;
    root2.insert("type",2);
    data_root.insert("flag","stop");
    root2.insert("data",data_root);

    QString text=QString(QJsonDocument(root2).toJson());
    char data[N]={};
    strcpy(data,text.toLatin1().data());
    tcp_socket->write(data,N);
    qDebug()<<"send2:"<<data;
}

void MyLogin::heartPackSendSlot()
{
    //下发type3 包
    QJsonObject root;
    root.insert("type", 3);
    QString text=QString(QJsonDocument(root).toJson());
    char data[N]={};
    strcpy(data,text.toLatin1().data());
    qDebug()<<"heart pack send:"<<data;
    tcp_socket->write(data,N);
    time_out_tm->start();
}

void MyLogin::TimeOutSlot()
{
    qDebug()<<"设备连接异常";
    QMessageBox::critical(this,"提示","设备连接异常");
    tcp_socket->close();
    //关闭界面
    //this->close();
}

void MyLogin::onIndexChanged(int index)
{    QJsonObject node_data;
     QJsonObject node_data_data;
     QJsonDocument document;
    if(index==0)
    {
        node_data_data.insert("type",index);
        node_data_data.insert("period",5);
        node_data.insert("type",3);
        node_data.insert("data",QJsonValue(node_data_data));
        document.setObject(node_data);
        QByteArray bytearray = document.toJson(QJsonDocument::Compact);
        QMQTT::Message message;
        message.setPayload(bytearray);
        message.setTopic("/app/data/down");
        GlobalVal::mqtt->publish(message);
    }
    if(index==1)
    {
        node_data_data.insert("type",index);
        node_data_data.insert("period",5);
        node_data.insert("type",3);
        node_data.insert("data",QJsonValue(node_data_data));
        document.setObject(node_data);
        QByteArray bytearray = document.toJson(QJsonDocument::Compact);
        QMQTT::Message message;
        message.setPayload(bytearray);
        message.setTopic("/app/data/down");
        GlobalVal::mqtt->publish(message);
    }
    if(index==2)
    {
        node_data_data.insert("type",index);
        node_data_data.insert("period",5);
        node_data.insert("type",3);
        node_data.insert("data",QJsonValue(node_data_data));
        document.setObject(node_data);
        QByteArray bytearray = document.toJson(QJsonDocument::Compact);
        QMQTT::Message message;
        message.setPayload(bytearray);
        message.setTopic("/app/data/down");
        GlobalVal::mqtt->publish(message);
    }
}

